<template>
  <div :class="classes" @mouseleave="handleMouseleave">
    <input type="hidden" :name="name" :value="currentValue">
    <div
      v-for="item in count"
      :class="starCls(item)" 
      @mousemove="handleMousemove(item, $event)"
      :key="item"
      @click="handleClick(item)"
    >
      <template v-if="!showCharacter">
        <div>
          <span :class="[prefixCls + '-star-content']" type="half"></span>
        </div>
      </template>
      <template v-else>
        <span :class="[prefixCls + '-star-first']" type="half">
          <template  v-if="character !== ''">{{ character }}</template>
          <i v-else :class="iconClasses" type="half"></i>
        </span>
        <span :class="[prefixCls + '-star-second']">
          <template v-if="character !== ''">{{ character }}</template>
          <i v-else :class="iconClasses"></i>
        </span>
      </template>
    </div>
    <div :class="[prefixCls + '-text']" v-if="showText" v-show="currentValue > 0">
      <slot><span>{{ currentValue }}</span> <span v-if="currentValue <= 1">{{ rateText }}</span><span v-else>{{ ratesText }}</span></slot>
    </div>
  </div>
</template>

<script>
import {defineComponent,ref,computed,watch,onMounted,getCurrentInstance} from "vue"
import Locale from "../../mixins/locale"
import mixinsForm from "../../mixins/form"
export default defineComponent({
  mixins:[Locale,mixinsForm],
  props:{
    count: {
      type: Number,
      default: 5
    },
    modelValue: {
      type: Number,
      default: 0
    },
    allowHalf: {
      type: Boolean,
      default: false
    },
    disabled: {
      type: Boolean,
      default: false
    },
    showText: {
      type: Boolean,
      default: false
    },
    name: {
      type: String
    },
    clearable: {
      type: Boolean,
      default: false
    },
    character: {
      type: String,
      default: ''
    },
    icon: {
      type: String,
      default: ''
    },
    customIcon: {
      type: String,
      default: ''
    }
  },
  emits: ['update:modelValue', 'on-change'],
  setup(props,context){
    const value=props.modelValue||0
    const _half=props.allowHalf&&value.toString().indexOf('.')>=0
    // console.log(context)
    const prefixCls=ref("haloe-rate")
    let currentValue=ref(value)
    let hoverIndex=ref(-1)
    let isHover=ref(false)
    let isHalf=ref(_half)

    const vm=getCurrentInstance()

    const classes=computed(()=>{
      return [
        `${prefixCls.value}`,
        {
          [`${prefixCls.value}-disabled`]:vm.ctx.itemDisabled
        }
      ]
    })

    const iconClasses=computed(()=>{
      return [
        'haloe-icon',
        {
          [`haloe-icon-${props.icon}`]:props.icon!=='',
          [`${props.customIcon}`]:props.customIcon!==''
        }
      ]
    })

    const showCharacter=computed(()=>{
      return props.character!==''||props.icon!==''||props.customIcon!=='';
    })

    const setHalf=(val)=>{
      isHalf.value=props.allowHalf&&val.toString().indexOf('.')>=0;
    }
    const starCls=(value)=>{
      const _hoverIndex=hoverIndex.value
      const currentIndex=isHover.value?_hoverIndex:currentValue.value
      
      let full=false
      let isLast=false;

      if(currentIndex>=value) full=true

      if(isHover.value){
        isLast=currentIndex===value
      }else{
        isLast=Math.ceil(currentValue.value)===value
      }

      return [
        {
          [`${prefixCls.value}-star`]:!showCharacter.value,
          [`${prefixCls.value}-star-chart`]:showCharacter.value,
          [`${prefixCls.value}-star-full`]:(!isLast&&full)||(isLast&&!isHalf.value),
          [`${prefixCls.value}-star-half`]:isLast&&isHalf.value,
          [`${prefixCls.value}-star-zero`]:!full
        }
      ]
    }

    const rateText=computed(()=>{
      return vm.ctx.t('i.rate.star')
    })

    const ratesText=computed(()=>{
      return vm.ctx.t("i.rate.stars")
    })

    const handleMousemove=(value, event)=>{
      if(vm.ctx.itemDisabled) return;
      isHover.value=true
      if(props.allowHalf){
        const type=event.target.getAttribute('type') || false;
        isHalf.value=type==='half';
      }else{
        isHalf.value=false
      }
      hoverIndex.value=value
    }

    const handleMouseleave=()=>{
      if(vm.ctx.itemDisabled) return

      isHover.value=false
      setHalf(currentValue.value)
      hoverIndex.value=-1
    }

    const handleClick=(value)=>{
      if(vm.ctx.itemDisabled) return

      if(isHalf.value) value-=0.5

      if(props.clearable&&Math.abs(value-currentValue.value)<0.01){
        value=0;
      }

      currentValue.value=value
      context.emit('update:modelValue', value);
      context.emit('on-change', value);
      // context.handleFormItemChange('change', value);
      vm.ctx.handleFormItemChange('change',value)
    }

    watch(()=>props.modelValue,(val)=>{
      currentValue.value=val||0
    })

    watch(()=>currentValue.value,(val)=>setHalf(val))

    return{
      prefixCls,
      currentValue,
      hoverIndex,
      classes,
      iconClasses,
      showCharacter,
      rateText,
      ratesText,

      handleClick,
      handleMouseleave,
      handleMousemove,
      starCls,
      setHalf,
    }
  }
})
</script>

<style>

</style>